/**
 * @file 添加文章-header组件
 * @author wangshaozhi(wangshaozhi@baidu.com)
 */

import {ChangeEvent, useCallback, useEffect, useRef, useState} from 'react';
import {observer} from 'mobx-react';
import {Button, DatePicker, Input, Select, message} from 'antd';
import moment, {Moment} from 'moment';
import {useHistory} from 'react-router-dom';
import {useTitle} from 'react-use';
import dayjs from 'dayjs';
import {MainStore} from '../../../../../store/mainStore';

// request
import request from '../../../../../request';

// style
import cls from './index.module.scss';
import {ADD_ARTICLE_URL, ARTICLE_TYPES_URL} from '../../../../../request/url';
import Article from '../../../../../model/article';

interface IProps {
    store: MainStore;
}

interface IType {
    value: Article.EArticleType;
    label: string;
}

export const Header: React.FC<IProps> = observer(({
    store
}) => {
    const {
        sideBarStore,
        articleStore: {
            currOperateArticle
        }
    } = store;
    const [typeList, setTypeList] = useState<IType[]>([]);
    const history = useHistory();
    const getArticleTypeNameRef = useRef<boolean>(true);
    const [currSaveDate, setCurrSaveDate] = useState<Date>(new Date());
    useTitle('添加/更新文章');

    const onPublishTimeChange = useCallback((date: Moment | null) => {
        const publishTime = dayjs(date?.toString()).format('YYYY-MM-DD');
        currOperateArticle?.update({
            publishTime
        });
    }, [currOperateArticle]);

    const onAddOrUpdateArticle = useCallback(async () => {
        const {
            id,
            title,
            content,
            publishTime,
            type,
            introduction,
            viewsCount,
            isDel,
            isPublish,
            cover
        } = currOperateArticle;

        const author = JSON.parse(localStorage.getItem('user') || '{}').username;

        try {
            const res = await request({
                method: 'post',
                url: ADD_ARTICLE_URL,
                data: {
                    id,
                    title,
                    content,
                    publishTime,
                    type,
                    introduction,
                    viewsCount: viewsCount ?? 0,
                    isDel,
                    isPublish,
                    author,
                    cover,
                    isSaved: Article.ESaved.SAVED
                }
            });
    
            const {code, msg} = res.data;
            if (code === 0) {
                message.success(msg);
                if (!id) {
                    history.push('/article/publish');
                    sideBarStore.update({
                        currSelectedKeys: ['article', 'publish']
                    });
                }
                else {
                    currOperateArticle.update({
                        isSaved: Article.ESaved.SAVED
                    });
                }
                return;
            }
        
            message.error(msg);
        }
        catch (e) {
            // TODO: 完善
        }
    }, [currOperateArticle, history, sideBarStore]);

    useEffect(() => {
        const getArticleTypeName = async () => {
            try {
                const res = await request({
                    method: 'get',
                    url: ARTICLE_TYPES_URL
                });

                const data = res.data;
                setTypeList(data.map((d: any) => ({
                    label: d.name,
                    value: d.id
                })));
            }
            catch(e) {

            }
        };

        if (getArticleTypeNameRef.current) {
            getArticleTypeName();
            getArticleTypeNameRef.current = false;
        }
        let timer: number = 0;

        timer = window.setInterval(() => {
            setCurrSaveDate(new Date());
            if (currOperateArticle.isSaved) {
                onAddOrUpdateArticle();
            }
        }, 30000);

        return () => {
            clearInterval(timer);
        }
    }, [currOperateArticle.isSaved, onAddOrUpdateArticle]);

    const onTitleChange = useCallback((e: ChangeEvent<HTMLInputElement>) => {
        const value = e.target.value;
        currOperateArticle?.update({
            title: value
        })
    }, [currOperateArticle]);

    const onArticleChange = useCallback((type: Article.EArticleType) => {
        currOperateArticle.update({
            type
        });
    }, [currOperateArticle]);

    const onCoverChange = useCallback((e: ChangeEvent<HTMLInputElement>) => {
        const value = e.target.value;
        currOperateArticle?.update({
            cover: value
        })
    }, [currOperateArticle]);

    return (
        <div className={cls.wrapper}>
            <div className={cls.titleOuterWrapper}>
                <div className={cls.titleWrapper}>
                    <span>文章标题：</span>
                    <Input
                        showCount
                        placeholder="请输入文章标题"
                        className={cls.titleInput}
                        maxLength={40}
                        value={currOperateArticle.title}
                        onChange={onTitleChange}
                    />
                </div>
                <Button
                    type="primary"
                    className={cls.saveDraftBtn}
                    onClick={onAddOrUpdateArticle}
                >
                    添加/更新文章
                </Button>
                {currOperateArticle.isSaved === Article.ESaved.SAVED && (
                    <div>
                        自动保存于{`${currSaveDate.toLocaleTimeString()}`}
                    </div>
                )}
            </div>
            <div className={cls.otherConfigWrapper}>
                <div className={cls.coverWrapper}>
                    <span>文章封面：</span>
                    <Input
                        placeholder="请输入文章封面链接"
                        value={currOperateArticle.cover}
                        onChange={onCoverChange}
                        className={cls.cover}
                    />
                </div>
                <div className={cls.typeAndDateWrapper}>
                    <span>文章类型：</span>
                    <Select
                        value={+currOperateArticle.type as Article.EArticleType}
                        onChange={onArticleChange}
                        options={typeList}
                    />
                    <div className={cls.publishDateWrapper}>
                        <span>发布日期：</span>
                        <DatePicker
                            placeholder="请选择文章日期"
                            onChange={onPublishTimeChange}
                            value={moment(currOperateArticle.publishTime)}
                        />
                    </div>
                </div>
            </div>
        </div>
    );
})